package org.easy.tool.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import org.easy.tool.common.*;
import org.easy.tool.entity.Knowledge;
import org.easy.tool.entity.Problem;
import org.easy.tool.entity.UserTrain;
import org.easy.tool.mapper.*;
import org.easy.tool.service.IUserTrain;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.*;

/**
 * <p>
 * 服务实现类
 * </p>
 *
 * @author Valley
 * @since 2025-06-16 20:51:13
 */
@Service
public class UserTrainService extends ServiceImpl<UserTrainMapper, UserTrain> implements IUserTrain {

    @Autowired
    UserMapper userMapper;

    @Autowired
    ProblemMapper problemMapper;

    @Autowired
    KnowledgeMapper knowledgeMapper;

    @Autowired
    UserTrainMapper userTrainMapper;

    private static final String trainKnowledge = "knowledge";

    /**
     * 返回需要的随机知识点
     */
    private void formKnowledge(LinkedHashMap data, Knowledge knowledge) {
        //返回需要训练的知识点信息
        data.put("title", knowledge.getName());
        data.put("type", "knowledge");
    }

    /**
     * 查询用户对某个知识点的训练记录
     */
    private List<UserTrain> getKnowledgeTrain(String userId, String knowledgeId) {
        LambdaQueryWrapper<UserTrain> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(UserTrain::getUserId, userId)
                .eq(UserTrain::getTrainType, trainKnowledge)
                .eq(UserTrain::getTrainId, knowledgeId);
        return list(wrapper);
    }

    /**
     * 输入yyyy-MM-dd HH:mm:ss返回yyyy-MM-dd HH:mm:ss
     * 根据训练次数和上次训练时间计算下次训练时间
     */
    private String calculateTrainTime(int trainNum, String lastTrainTime) {
        String calculateTime = StringUtil.sub(lastTrainTime, 0, 10);
        if (trainNum <= 3) {
            calculateTime = TimeUtil.ymdFutureYMD(calculateTime, 1);
        } else if (trainNum <= 7) {
            calculateTime = TimeUtil.ymdFutureYMD(calculateTime, 2);
        } else if (trainNum <= 10) {
            calculateTime = TimeUtil.ymdFutureYMD(calculateTime, 3);
        }
        return calculateTime + " 00:00:00";
    }

    @Override
    public Object submitTrain(LinkedHashMap data) {
        String userId = WebUtil.getUserId();
        String trainType = (String) data.get("trainType");
        String trainId = (String) data.get("trainId");
        String result = (String) data.get("result");
        Integer costTime = (Integer) data.get("costTime");
        String id = "";
        //仅实现了知识点
        if (trainKnowledge.equals(trainType)) {
            List<UserTrain> userTrainList = getKnowledgeTrain(userId, trainId);
            if (userTrainList.size() < 10) {
                UserTrain userTrain = new UserTrain();
                userTrain.setTrainType(trainType);
                userTrain.setUserId(userId);
                userTrain.setResult(result);
                userTrain.setTrainId(trainId);
                userTrain.setUpdateTime(TimeUtil.nowMS());
                userTrain.setCreateTime(TimeUtil.nowMS());
                userTrain.setCostTime(costTime);
                save(userTrain);
                id = userTrain.getId();
            }
        }
        return id;
    }

    @Override
    public Object judgeBlankAnswer(LinkedHashMap data) {
        String reply = (String) data.get("answer");
        String problemId = (String) data.get("problemId");
        Problem problem = problemMapper.selectById(problemId);
        String content = problem.getContent();
        String answer = JSONUtil.parse(content, "answer") + "";
        return StringUtil.judgeEqualNumStr(answer, reply);
    }

    /**
     * 组装知识点全路径名字
     */
    public String formKnowledgeName(Knowledge knowledge) {
        StringBuilder name = new StringBuilder(knowledge.getName());
        Knowledge formKnowledge = knowledgeMapper.selectById(knowledge.getPid());
        for (int i = 0; i < 3; i++) {
            if (formKnowledge != null) {
                name.insert(0, formKnowledge.getName() + "  ");
                formKnowledge = knowledgeMapper.selectById(formKnowledge.getPid());
            }
        }
        return name.toString();
    }

    @Override
    public Object study(LinkedHashMap reqData) {
        LinkedHashMap data = new LinkedHashMap();
        //查询用户历史训练状态判断用户下一个训练知识点是什么
        List<Knowledge> studyKnowledge = todayNeedTrain();
        if (studyKnowledge.size() == 0) {
            data.put("status", "completed");
            return data;
        }
        Knowledge knowledge = studyKnowledge.get(0);
        data.put("knowledgeId", knowledge.getId());
        data.put("knowledgeName", formKnowledgeName(knowledge));
        formKnowledge(data, knowledge);
        return data;
    }

    private String calculateLevel(int trained) {
        //初入江湖，初学乍练，登堂入室，炉火纯青，出类拔萃，神乎其技，超凡入圣，天人合一
        String level = "";
        if (trained < 100) {
            level = "Level 1(初入江湖)";
        } else if (trained < 300) {
            level = "Level 2(初学乍练)";
        } else if (trained < 500) {
            level = "Level 3(登堂入室)";
        } else if (trained < 800) {
            level = "Level 4(炉火纯青)";
        } else if (trained < 1000) {
            level = "Level 5(出类拔萃)";
        } else if (trained < 1500) {
            level = "Level 6(神乎其技)";
        } else if (trained < 2000) {
            level = "Level 7(超凡入圣)";
        } else {
            level = "Level 8(天人合一)";
        }
        return level;
    }

    /**
     * 判断当前知识点今天是否要进行训练
     */
    private boolean judgeTodayTrain(List<UserTrain> userTrainList) {
        if (userTrainList == null || userTrainList.size() == 0) return true;
        if (userTrainList.size() >= 10) return false;
        int trainNum = userTrainList.size();
        userTrainList.sort((a, b) -> {
            long aTime = TimeUtil.msToTimeStamp(a.getCreateTime());
            long bTime = TimeUtil.msToTimeStamp(b.getCreateTime());
            return (int) (bTime - aTime);
        });
        UserTrain lastTrain = userTrainList.get(0);
        String lastTrainTime = lastTrain.getCreateTime();
        String nextTrainTime = calculateTrainTime(trainNum, lastTrainTime);
        return TimeUtil.judgeLast(nextTrainTime);

    }

    /**
     * 获取用户今日已训练的知识点
     */
    private List<UserTrain> todayTrained() {
        String userId = WebUtil.getUserId();
        String today = TimeUtil.todayYMD();
        LambdaQueryWrapper<UserTrain> userTrainWrapper = new LambdaQueryWrapper<>();
        userTrainWrapper.eq(UserTrain::getUserId, userId).like(UserTrain::getCreateTime, today);
        return list(userTrainWrapper);
    }

    /**
     * 用户完成的全部知识点
     */
    private List<UserTrain> userAllTrained(String userId){
        LambdaQueryWrapper<UserTrain> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(UserTrain::getUserId, userId);
        return list(wrapper);
    }

    private String totalTrainedTime(List<UserTrain> userTrainList){
        int costTime = 0;
        for (UserTrain userTrain : userTrainList) {
            costTime += userTrain.getCostTime();
        }
        return TimeUtil.secondToFormatText(costTime);
    }

    @Override
    public Object getUserTrainSummary(LinkedHashMap data) {
        LinkedHashMap resData = new LinkedHashMap();
        resData.put("knowledgeCount", 100);
        resData.put("trainCount", 100);
        resData.put("level", "Level1");
        resData.put("trained", 42);
        resData.put("trainedTime", "100小时");
        resData.put("todayTrained", 34);
        resData.put("todayTrainedTime", "88小时");
        resData.put("todayNeedTrain", 13);
        resData.put("percent", 0.66);
//        LambdaQueryWrapper<Knowledge> knowledgeWrapper = new LambdaQueryWrapper<>();
//        //隐藏的知识点不训练
//        knowledgeWrapper.ne(Knowledge::getDeleted, "hide");
//        //入库的知识点数量
//        int knowledgeCount = knowledgeMapper.selectList(knowledgeWrapper).size();
//        resData.put("knowledgeCount", knowledgeCount);
//        String userId = WebUtil.getUserId();
//        LambdaQueryWrapper<UserTrain> userTrainWrapper = new LambdaQueryWrapper<>();
//        userTrainWrapper.eq(UserTrain::getTrainType, "knowledge").eq(UserTrain::getUserId, userId);
//        List<UserTrain> list = list(userTrainWrapper);
//        //总共需要完成的训练次数
//        int trainCount = knowledgeCount * 10;
//        resData.put("trainCount", trainCount);
//        //当前总共已完成的训练次数
//        List<UserTrain> userTrainedList = userAllTrained(WebUtil.getUserId());
//        int trained = userTrainedList.size();
//        resData.put("level", calculateLevel(trained));
//        resData.put("trained", trained);
//        resData.put("trainedTime", totalTrainedTime(userTrainedList));
//        //今日已完成的训练次数
//        List<UserTrain> todayUserTrainedList = todayTrained();
//        int todayTrained = todayUserTrainedList.size();
//        resData.put("todayTrained", todayTrained);
//        resData.put("todayTrainedTime", totalTrainedTime(todayUserTrainedList));
//        //今日还需要完成的训练次数
//        int todayNeedTrain = todayNeedTrain().size();
//        resData.put("todayNeedTrain", todayNeedTrain);
//        double percent = 1.0 * trained / trainCount;
//        String percentPoint = NumUtil.percentPoint(percent, 2).replaceAll("%", "");
//        resData.put("percent", Double.parseDouble(percentPoint));
        return resData;
    }

    private void sortKnowledge(List<Knowledge> knowledgeList) {
        knowledgeList.sort(Comparator.comparingInt(Knowledge::getSort));
    }

    private void recurSortKnowledge(List<Knowledge> sortKnowledge, String pid) {
        List<Knowledge> knowledgeList = knowledgeMapper.getKnowledgeListByPid(pid);
        if (knowledgeList == null || knowledgeList.size() == 0) return;
        sortKnowledge(knowledgeList);
        for (Knowledge knowledge : knowledgeList) {
            sortKnowledge.add(knowledge);
            recurSortKnowledge(sortKnowledge, knowledge.getId());
        }
    }

    /**
     * 获取排好序的知识点（包括学科、章节、知识点）
     */
    private List<Knowledge> getSortSubjectKnowledgeList() {
        List<Knowledge> sortKnowledgeList = new ArrayList<>();
        recurSortKnowledge(sortKnowledgeList, "root");
        return sortKnowledgeList;
    }

    private List<Knowledge> getSortKnowledgeList() {
        List<Knowledge> subjectKnowledgeList = getSortSubjectKnowledgeList();
        return subjectKnowledgeList;
    }

    /**
     * 查询今日所有需要完成的知识点 TODO 需要优化
     */
    private List<Knowledge> todayNeedTrain() {
        //方案一：按照预定的排序依次训练
        List<Knowledge> knowledgeList = new ArrayList<>();
        List<Knowledge> sortKnowledgeList = getSortKnowledgeList();
        String userId = WebUtil.getUserId();
        for (Knowledge knowledge : sortKnowledgeList) {
            //如果是已隐藏的知识点，则不训练
            if (!"hide".equals(knowledge.getDeleted())){
                List<UserTrain> userTrainList = getKnowledgeTrain(userId, knowledge.getId());
                if (judgeTodayTrain(userTrainList)) {
                    knowledgeList.add(knowledge);
                }
            }
        }
        return knowledgeList;
    }

}
